package com.hzw.saas.service.ds.service;

import com.baomidou.mybatisplus.extension.service.IService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.hzw.saas.api.ds.IHeartbeatLogService;
import com.hzw.saas.api.ds.bo.OnlineDeviceBo;
import com.hzw.saas.api.ds.query.OnlineDeviceQuery;
import com.hzw.saas.common.config.util.RedisUtil;
import com.hzw.saas.common.util.MapperUtil;
import com.hzw.saas.common.util.constants.CacheConsts;
import com.hzw.saas.service.ds.mapper.HeartbeatLogMapper;
import com.hzw.saas.service.ds.model.HeartbeatLog;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import java.time.LocalDateTime;
import java.util.*;
import java.util.stream.Collectors;

@Service
public class HeartbeatLogServiceImpl extends ServiceImpl<HeartbeatLogMapper, HeartbeatLog> implements IHeartbeatLogService, IService<HeartbeatLog> {

    @Override
    public List<OnlineDeviceBo> getOnlineDevices(OnlineDeviceQuery onlineDeviceQuery) {
        LocalDateTime now = LocalDateTime.now();
        Map<String, HeartbeatLog> cacheMap = new HashMap<>();
        Set<String> queryPidCollection = new HashSet<>();

        if (!RedisUtil.hasKey(CacheConsts.KEY_DS_HEARTBEAT_INTERVAL)) {
            return Collections.emptyList();
        }
        Integer interval = RedisUtil.get(CacheConsts.KEY_DS_HEARTBEAT_INTERVAL);
        super.lambdaQuery()
                .eq(HeartbeatLog::getUserId, onlineDeviceQuery.getUserId())
                .eq(HeartbeatLog::getClientType, onlineDeviceQuery.getClientType())
                .ge(HeartbeatLog::getCreateTime, now.minusSeconds(interval * 2))
                .list()
                .forEach(heartbeatLog -> queryPidCollection.add(heartbeatLog.getParentId()));
        if (!CollectionUtils.isEmpty(queryPidCollection)) {
            super.lambdaQuery()
                    .in(HeartbeatLog::getPid, queryPidCollection)
                    .list()
                    .forEach(heartbeatLog -> cacheMap.putIfAbsent(heartbeatLog.getPid(), heartbeatLog));
        }
        return cacheMap.values()
                .stream()
                .sorted(Comparator.comparing(HeartbeatLog::getCreateTime).reversed())
                .map(log -> MapperUtil.nf().map(log, OnlineDeviceBo.class).setLastLoginTime(log.getCreateTime()))
                .collect(Collectors.toList());
    }

}
